home *** CD-ROM | disk | FTP | other *** search
/ MacFormat 1997 November / MacFormat 056 (November 1997).dmg / Shareware Plus / Developers / Sierra Engine in Director / Script < prev   
Encoding:
Text File  |  1997-07-28  |  10.7 KB  |  226 lines  |  [TEXT/TBB6]

  1. -- This script was created by DaFedz, dafedz@usa.net, for use by anyone who wants to make
  2. -- a Sierra style game in director, but can't get a good engine for the way the character
  3. -- moves to the mouse click.  Any of this code may be used in a program, you don't even need
  4. -- to give me credit (you can if you want to, in which case just include my name and email
  5. -- address).  I hope this can be of some help.  The only thing I request is that I get a free
  6. -- copy of any games you make using this engine.  Again, this is purely optional, but I will
  7. -- use all such positive or negative feedback to determine whether I will make other public
  8. -- domain projects like this one in the future.
  9.  
  10. -- I'm fairly sure that this script will work in any version of director past version 4.
  11. -- It was made in Director 6, but I'm not using any advanced Lingo that wasn't available
  12. -- in 4 or 5.
  13.  
  14. --                       --->•!!! MAKING GAMES IN DIRECTOR !!!•<---
  15.  
  16. -- What's this?  Director can't make fast games?  You can't have truly interactive games
  17. -- made by director that are still fast and fun?  You could never create a good engine for
  18. -- a fun game in director, such as the Sierra-style engine?  You've tried to do it and always
  19. -- came up with an engine that is very inaccurate because of the rounding done to your numbers
  20. -- to fit the pixels on the screen?
  21.  
  22. -- WRONG!!
  23.  
  24. -- It's true that it's harder with the scripting language Lingo to make and engine where
  25. -- a sprite moves from a stationary position to a click location, but it is possible, even
  26. -- with a reasonably short amount of coding.  The way I worked it out is that the sprite
  27. -- has 16 basic angles to move on a 360° scale.  The engine checks which of these angles
  28. -- is best to reach the goal and moves in that direction, it then checks again and moves
  29. -- again, checks then moves, checks then moves.  This way the sprite will always reach the
  30. -- click point accurately in a more or less straight line.
  31.  
  32. --     4     1       2
  33. --     |     /      /     This is a crude ASCII representation of one quadrant on a 360°
  34. --     |    |     /       scale that the sprite can move in along with the numbers used
  35. --     |   /    /    3    in the variable that stores which angle the sprite is moving in.
  36. --     |  |   /   __/     The ratios of vertical movement to horizontal movement are:
  37. --     | /  /  __/
  38. --     || / __/           0) 1:0  1) 1:2  2) 1:1  3) 2:1  4) 0:1
  39. --     |/__/
  40. --     *-------------0    If you take the numbers in between these ratios you come up with
  41. --                        a range around each angle.  This is the range that decides what
  42. -- angle to use.  If the click falls within a range around angle 2 (boundaries being between
  43. -- angles 1 and 2 as well as angles 3 and 2) then angle 2 will be used for the next move.
  44.  
  45. -- I found that my engine where the ratio derived directly from the origin and destination
  46. -- was used to move the sprite was very inaccurate and unpredictable.  The sprite would often
  47. -- end up over 100 pixels away from where I clicked.  I found that limiting the angles of
  48. -- movement to 16 greatly increased the accuracy as well as useability of the engine.  Using
  49. -- an engine like this it would not be hard to incorporate keyboard control of the sprite,
  50. -- boundaries, and areas where the sprite moves around rather than through.
  51.  
  52. -- Enough comment header, on to the actual coding.
  53.  
  54. global mhorz    --The horizontal position of the clock location
  55. global mvert    --The vertical position of the click location
  56. global hdist    --The horizontal distance from the sprite to the click location
  57. global vdist    --The vertical distance from the sprite to the click location
  58. global svert    --The vertical position of the sprite
  59. global shorz    --The horizontal position of the sprite
  60. global hdir     --The horizontal direction the sprite must move in (1 or -1)
  61. global vdir     --The vertical direction the sprite must move in (1 or -1)
  62. global movetype --The type of movement (which angle)
  63. global dratio   --The ratio to determin the angle needed to move in (vdist / hdist)
  64. global ismoving --Boolean whether the sprite is currently moving or not
  65. global t1var    --Variable used in type 1 angle to alternate the vertical movement
  66. global t3var    --Variable used in type 3 angle to alternate the horizontal movement
  67. global speed    --The speed at which the sprite moves (in pixels)
  68.  
  69. on startmovie
  70.   set speed to 10 --Can vary, depends on smoothness wanted
  71.   set the puppet of sprite 1 to true --Allows lingo to control the sprite in channel 1
  72.   set ismoving to false --The sprite starts off stationary
  73. end
  74.  
  75. -- Calcpath is the handler that calculates the angle that the sprite moves in.  It is
  76. -- important to call this constantly while the sprite is moving (ismoving is true).
  77. -- Since we want to be able to change the direction of the sprite even when it is already
  78. -- moving, we should call calcpath on idle and make calcpath move the sprite one jump
  79. -- at a time (a jump being the number of pixels that is in the speed variable).
  80.  
  81. on idle
  82.   if ismoving = true then calcpath
  83. end idle
  84.  
  85. on mousedown
  86.   put the mousev into mvert --Gets the vertical location of the mouse
  87.   put the mouseh into mhorz --Gets the horizontal location of the mouse
  88.   put the locv of sprite 1 into svert --Gets the vertical location of the sprite
  89.   put the loch of sprite 1 into shorz --Gets the horizontal location of the sprite
  90.   calcpath --The first call to calculate the angle to move in
  91.   updatestage
  92. end
  93.  
  94. on calcpath
  95.   
  96.   -- Now to find the ratio we put the absolute value (non-negative number) of the
  97.   -- mouse positions minus the sprite positions and divide them.  If the vertical
  98.   -- difference is zero then we can automatically set the ange to type 4, and if
  99.   -- the horizontal difference is zero we can set the type to 0.
  100.   
  101.   put abs(mvert - svert) into vdist
  102.   put abs(mhorz - shorz) into hdist
  103.   if float(vdist) <> 0 then
  104.     if float(hdist) <> 0 then
  105.       put float(vdist) / float(hdist) into dratio
  106.     else
  107.       put 0 into dratio
  108.     end if
  109.   else
  110.     put 4 into dratio
  111.   end if
  112.   
  113.   -- Now we test the ratio to decide the type of angle to use.  See the comment at
  114.   -- the top of this script to see how this was derived.
  115.   
  116.   if dratio < 0.25 then set movetype to 0
  117.   if dratio >= 0.25 and dratio < 0.75 then set movetype to 1
  118.   if dratio >= 0.75 and dratio < 1.5 then set movetype to 2
  119.   if dratio >= 1.5 and dratio < 4 then set movetype to 3
  120.   if dratio >= 4 then set movetype to 4
  121.   
  122.   -- Now we check what quadrant the click was in compared to the sprite and set the
  123.   -- vertical and horizontal directions accordingly (i.e., if the click was to the
  124.   -- right of, and below the sprite, the horizontal will be negative and the vertical
  125.   -- will be positive.)
  126.   
  127.   if mvert <= svert and mhorz >= shorz then
  128.     set hdir to speed
  129.     set vdir to -speed
  130.   end if
  131.   if mvert >= svert and mhorz <= shorz then
  132.     set hdir to -speed
  133.     set vdir to speed
  134.   end if
  135.   if mvert >= svert and mhorz >= shorz then
  136.     set hdir to speed
  137.     set vdir to speed
  138.   end if
  139.   if mvert <= svert and mhorz <= shorz then
  140.     set hdir to -speed
  141.     set vdir to -speed
  142.   end if
  143.   
  144.   -- We now have all the information we need to move the sprite.
  145.   
  146.   set ismoving to true --Start it rolling
  147.   set the castNum of sprite 1 to 1 --Here you can switch to an alternate cast member
  148.   --                                 while the sprite is in motion
  149.   moveit --This handler will move the sprite one jump as well as check to see when the
  150.   --       sprite has reached it's destination
  151. end
  152.  
  153. on moveit
  154.   if movetype = 0 then --Angle zero moves the sprite 1 jump horizontally
  155.     set shorz to shorz + hdir
  156.   end if
  157.   
  158.   -- Angle 1 uses a variable that adds to 2 and resets constantly so that the sprite
  159.   -- will only move once vertically every other time.  This way it will move
  160.   -- horizontally twice for every vertical move.
  161.   
  162.   if movetype = 1 then
  163.     set shorz to shorz + hdir
  164.     set t1var to t1var + 1
  165.     if t1var = 2 then
  166.       set svert to svert + vdir
  167.       set t1var to 0
  168.     end if
  169.   end if
  170.   if movetype = 2 then --Moves one jump vertically and one horizontally
  171.     set shorz to shorz + hdir
  172.     set svert to svert + vdir
  173.   end if
  174.   
  175.   -- Angle 3 uses a variable that adds to 2 and resets constantly so that the sprite
  176.   -- will only move once horizontally every other time.  This way it will move
  177.   -- vertically twice for every horizontal move.
  178.   
  179.   if movetype = 3 then
  180.     set svert to svert + vdir
  181.     set t3var to t3var + 1
  182.     if t3var = 2 then
  183.       set shorz to shorz + hdir
  184.       set t3var to 0
  185.     end if
  186.   end if
  187.   if movetype = 4 then --Moves the sprite one jump vertically
  188.     set svert to svert + vdir
  189.   end if
  190.   set ismoving to true --Sets it so calcpath will be called on idle
  191.   set the loch of sprite 1 to shorz --Sets the sprite to the new horizontal position
  192.   set the locv of sprite 1 to svert --Sets the sprite to the new vertical position
  193.   updatestage
  194.   
  195.   -- Now we must check to see if the sprite has completed it's move with the jump that
  196.   -- it just made.  Since we are moving the sprite by a number of pixels other than 1,
  197.   -- we have to check if the sprite is within close enough proximity to the click so that
  198.   -- if one more jump were made by a number of pixels less than that of the current
  199.   -- speed setting, the sprite would reach the click location.
  200.   
  201.   if shorz < mhorz + speed and shorz > mhorz - speed and svert < mvert + speed ¬
  202.   and svert > mvert - speed then
  203.     set ismoving to false --Stop it from moving
  204.     set the castNum of sprite 1 to 3 --Return the sprite to the original cast member
  205.     set the loch of sprite 1 to mhorz --Set the sprite to the click position exactly
  206.     set the locv of sprite 1 to mvert --Set the sprite to the click position exactly
  207.     updatestage
  208.   end if
  209. end
  210.  
  211. -- From here it should not be too hard to set boundaries of movement with another
  212. -- handler as well as objects that act as obstacles.  I would suggest giving such
  213. -- an object it's own script with it's boundaries along with what angle must be moved
  214. -- at to pass that boundary.  The sprite can be made to move in this angle while
  215. -- constantly checking if it's target can be reached by a straight line until it can.
  216.  
  217. -- Future projects that I might take on (in fact I will as soon as I start my game) are things
  218. -- like scaling the sprite as it moves farther away and closer, a good modular method of
  219. -- incorporating boundaries and obstacles, and perhaps attempting a crude (VERY crude) 3D
  220. -- Doom-type engine using Director (this would be a feat).  Anyways, you can always feel free
  221. -- to email me and ask me what I've done and I might provide you with some code to help you
  222. -- along.  Anything for a fellow programmer!
  223.  
  224. -- Good luck, and happy Directing!
  225. --                                                                      DaFedz
  226. --                                                                      dafedz@usa.net